<template>
  <div ref="container" class="scroll-x-container" :style="{ height: height }">
    <div
      ref="content"
      :class="[
        'scroll-x-content',
        { centered: !isOverflow && align === 'center' },
        { left: !isOverflow && align === 'left' },
        { right: !isOverflow && align === 'right' },
      ]"
      :style="contentStyle"
      @mouseenter="pauseScroll"
      @mouseleave="resumeScroll"
    >
      <div ref="slotWrap" class="slot-wrap">
        <slot />
      </div>
      <div v-if="isOverflow" class="slot-wrap">
        <slot />
      </div>
    </div>
  </div>
</template>

<script>
import { debounce } from "lodash"; // 使用 lodash 的 debounce

export default {
  name: "ScrollXNew",
  props: {
    // 以1920px为基准，单位：像素/秒，默认30
    speed: {
      type: Number,
      default: 30,
    },
    // 容器高度
    height: {
      type: [String, Number],
      default: "100%",
    },
    align: {
      type: String,
      default: "center",
      validator: (value) => ["left", "center", "right"].includes(value),
    },
    // 新增：是否启用滚动
    enabled: {
      type: Boolean,
      default: true,
    },
  },
  data() {
    return {
      isOverflow: false,
      animationFrame: null,
      scrollLeft: 0,
      containerWidth: 0,
      contentWidth: 0,
      running: true,
      observer: null,
      resizeObserver: null,
      isVisible: true, // 新增：控制组件是否可见
      isMounted: false, // 新增：标记组件是否已挂载
      // 新增：浏览器兼容性相关
      isModernBrowser: true,
      fallbackInterval: null,
      lastTimestamp: 0,
      // 新增：滚动方向
      direction: 1, // 1: 从右向左, -1: 从左向右
    };
  },
  computed: {
    // 根据屏幕宽度自适应速度
    realSpeed() {
      const baseScreen = 1920;
      const currentScreen = window.innerWidth || baseScreen;
      return (this.speed * currentScreen) / baseScreen;
    },
    contentStyle() {
      if (this.isModernBrowser) {
        return {
          transform: this.isOverflow ? `translateX(-${this.scrollLeft}px)` : "none",
          whiteSpace: "nowrap",
          transition: "none",
          width: this.isOverflow ? this.contentWidth * 2 + "px" : "auto",
          display: "flex",
          willChange: "transform",
          backfaceVisibility: "hidden",
          perspective: 1000,
          transformStyle: "preserve-3d"
        };
      } else {
        // 降级方案：使用 marginLeft
        return {
          marginLeft: this.isOverflow ? `-${this.scrollLeft}px` : "0",
          whiteSpace: "nowrap",
          transition: "none",
          width: this.isOverflow ? this.contentWidth * 2 + "px" : "auto",
          display: "flex"
        };
      }
    },
  },
  watch: {
    // 新增：监听 enabled 属性变化
    enabled: {
      handler(newVal) {
         if (newVal && this.isMounted) {
          this.checkOverflow();
        } else {
          this.stopScroll();
        }
      },
      immediate: true,
    },
  },
  mounted() {
    // 检测浏览器版本
    this.checkBrowserCompatibility();
    this.$nextTick(() => {
      this.isMounted = true;
      this.initObservers();
      this.checkOverflow();
    });
  },
  beforeDestroy() {
    this.destroyObservers();
    this.stopScroll();
  },
  methods: {
    // 新增：检测浏览器兼容性
    checkBrowserCompatibility() {
      const ua = navigator.userAgent;
      const chromeVersion = ua.match(/Chrome\/(\d+)/);
      this.isModernBrowser = chromeVersion && parseInt(chromeVersion[1]) >= 50;
    },
    initObservers() {
      if (!this.isMounted) return;
      if (!this.$refs.slotWrap) return;
      // 使用防抖函数包装 checkOverflow
      const debouncedCheckOverflow = debounce(this.checkOverflow, 100);

      // 监听 slot 内容变化
      this.observer = new MutationObserver(debouncedCheckOverflow);
      this.observer.observe(this.$refs.slotWrap, {
        childList: true,
        subtree: true,
        characterData: true,
        attributes: true,
      });

      // 监听容器大小变化
      if (window.ResizeObserver) {
        this.resizeObserver = new ResizeObserver(debouncedCheckOverflow);
        this.resizeObserver.observe(this.$refs.container);
        this.resizeObserver.observe(this.$refs.slotWrap);
      }

      // 监听窗口大小变化（使用事件委托）
      window.addEventListener("resize", debouncedCheckOverflow);
    },
    destroyObservers() {
      if (this.observer) {
        this.observer.disconnect();
        this.observer = null;
      }
      if (this.resizeObserver) {
        this.resizeObserver.disconnect();
        this.resizeObserver = null;
      }
      window.removeEventListener("resize", this.debouncedCheckOverflow);
    },
    checkOverflow() {
      // 确保组件已挂载且 DOM 元素存在
      if (!this.isMounted || !this.enabled || !this.isVisible) return;
      if (!this.$refs.container || !this.$refs.slotWrap) return;

      this.$nextTick(() => {
        try {
          this.containerWidth = this.$refs.container.offsetWidth;
          this.contentWidth = this.$refs.slotWrap.scrollWidth;
          const tolerance = 1; // 添加容差值
          this.isOverflow = this.contentWidth > this.containerWidth + tolerance;

          if (this.isOverflow) {
            this.startScroll();
          } else {
            this.stopScroll();
            this.scrollLeft = 0;
          }
        } catch (error) {
          console.warn('ScrollX checkOverflow error:', error);
        }
      });
    },
    startScroll() {
      if (this.animationFrame || !this.isOverflow || !this.enabled || !this.isVisible) return;
      this.running = true;
      this.lastTimestamp = 0;

      if (this.isModernBrowser) {
        // 现代浏览器使用 requestAnimationFrame
        const step = (timestamp) => {
          if (!this.running || !this.isOverflow || !this.enabled || !this.isVisible) return;

          if (!this.lastTimestamp) {
            this.lastTimestamp = timestamp;
            this.animationFrame = requestAnimationFrame(step);
            return;
          }

          const delta = timestamp - this.lastTimestamp;
          this.lastTimestamp = timestamp;

          this.scrollLeft += (this.realSpeed * delta * this.direction) / 1000;

          // 重置滚动位置
          if (this.scrollLeft >= this.contentWidth) {
            this.scrollLeft = 0;
          } else if (this.scrollLeft <= 0) {
            this.scrollLeft = this.contentWidth;
          }

          this.animationFrame = requestAnimationFrame(step);
        };

        this.animationFrame = requestAnimationFrame(step);
      } else {
        // 降级方案：使用 setInterval
        this.fallbackInterval = setInterval(() => {
          if (!this.running || !this.isOverflow || !this.enabled || !this.isVisible) {
            this.stopScroll();
            return;
          }

          this.scrollLeft += this.realSpeed * this.direction;

          // 重置滚动位置
          if (this.scrollLeft >= this.contentWidth) {
            this.scrollLeft = 0;
          } else if (this.scrollLeft <= 0) {
            this.scrollLeft = this.contentWidth;
          }
        }, 16); // 约60fps
      }
    },
    stopScroll() {
      this.running = false;
      if (this.animationFrame) {
        cancelAnimationFrame(this.animationFrame);
        this.animationFrame = null;
      }
      if (this.fallbackInterval) {
        clearInterval(this.fallbackInterval);
        this.fallbackInterval = null;
      }
    },
    pauseScroll() {
      if (!this.isOverflow || !this.enabled || !this.isVisible) return;
      this.running = false;
      if (this.animationFrame) {
        cancelAnimationFrame(this.animationFrame);
        this.animationFrame = null;
      }
      if (this.fallbackInterval) {
        clearInterval(this.fallbackInterval);
        this.fallbackInterval = null;
      }
    },
    resumeScroll() {
      if (!this.running && this.isOverflow && this.enabled && this.isVisible) {
        this.running = true;
        this.lastTimestamp = 0;
        this.startScroll();
      }
    },
    // 新增：显示/隐藏组件
    show() {
      this.isVisible = true;
      this.checkOverflow();
    },
    hide() {
      this.isVisible = false;
      this.stopScroll();
    },
  },
};
</script>

<style scoped>
.scroll-x-container {
  width: 100%;
  max-height: 100%;
  position: relative;
  overflow-x: hidden;
  /* 添加硬件加速 */
  transform: translateZ(0);
  -webkit-transform: translateZ(0);
  backface-visibility: hidden;
  perspective: 1000;
}
.scroll-x-content {
  max-height: 100%;
  will-change: transform;
  /* 默认左对齐，滚动时用 */
  display: inline-block;
  white-space: nowrap;
  height: 100%;
  /* 添加硬件加速 */
  transform: translateZ(0);
  -webkit-transform: translateZ(0);
  backface-visibility: hidden;
  perspective: 1000;
}
.scroll-x-content.left {
  display: flex;
  justify-content: flex-start;
  align-items: center;
  white-space: normal;
  transform: none !important;
}

.scroll-x-content.right {
  display: flex;
  justify-content: flex-end;
  align-items: center;
  white-space: normal;
  transform: none !important;
}
.scroll-x-content.centered {
  /* 未溢出时居中 */
  display: flex;
  justify-content: center;
  align-items: center;
  white-space: normal;
  transform: none !important; /* 禁止动画 */
}
.slot-wrap {
  display: inline-flex;
  align-items: center;
  white-space: nowrap;
  height: 100%;
  /* 避免内容间有间隙 */
  margin: 0;
  padding: 0;
  overflow-y: hidden;
  /* 添加硬件加速 */
  transform: translateZ(0);
  -webkit-transform: translateZ(0);
  backface-visibility: hidden;
  perspective: 1000;
}
</style>
